package com.kzw.oa.comm.utils;

import java.lang.reflect.Proxy;
import java.sql.Connection;
import java.sql.DatabaseMetaData;
import java.sql.SQLException;
import java.util.Properties;

import javax.sql.DataSource;

import org.apache.commons.beanutils.BeanUtils;

public class ExtdbUtils {
	
	private final static ThreadLocal<Connection> conns = new ThreadLocal<Connection>();
	private static DataSource dataSource;
	private static boolean showSql = false;
	
	static {
		initDataSource(null);
	}

	/**
	 * 初始化连接池
	 */
	private final static void initDataSource(Properties dbProperties) {
		try {
			if(dbProperties == null){
				dbProperties = new Properties();
				dbProperties.load(ExtdbUtils.class.getResourceAsStream("/conf/config.properties"));
			}
			Properties props = new Properties();
			for(Object key : dbProperties.keySet()) {
				String skey = (String)key;
				if(skey.startsWith("db1.")){
					String name = skey.substring(4);
					props.put(name, dbProperties.getProperty(skey));
					if("show_sql".equalsIgnoreCase(name)){
						showSql = "true".equalsIgnoreCase(dbProperties.getProperty(skey));
					}
				}
			}
			dataSource = (DataSource)Class.forName(props.getProperty("datasource")).newInstance();
			if(dataSource.getClass().getName().indexOf("c3p0")>0){
				//Disable JMX in C3P0
				System.setProperty("com.mchange.v2.c3p0.management.ManagementCoordinator", 
						"com.mchange.v2.c3p0.management.NullManagementCoordinator");
			}
			System.out.println("Using DataSource : " + dataSource.getClass().getName());
			BeanUtils.populate(dataSource, props);

			Connection conn = getConn();
			DatabaseMetaData mdm = conn.getMetaData();
			System.out.println("Connected to " + mdm.getDatabaseProductName() + 
                              " " + mdm.getDatabaseProductVersion());
			closeConn();
		} catch (Exception e) {
			throw new RuntimeException(e);
		}
	}
	
	/**
	 * 断开连接池
	 */
	public final static void closeDataSource(){
		try {
			dataSource.getClass().getMethod("close").invoke(dataSource);
		} catch (NoSuchMethodException e){ 
		} catch (Exception e) {
			System.err.println("Unabled to destroy DataSource!!! " + e.getMessage());
		}
	}

	public final static Connection getConn() throws SQLException {
		Connection conn = conns.get();
		if(conn ==null || conn.isClosed()){
			conn = dataSource.getConnection();
			conns.set(conn);
		}
		return (showSql && !Proxy.isProxyClass(conn.getClass()))?
                      new DebugConnection(conn).getConnection():conn;
	}
	
	/**
	 * 关闭连接
	 */
	public final static void closeConn() {
		Connection conn = conns.get();
		try {
			if(conn != null && !conn.isClosed()){
				conn.setAutoCommit(true);
				conn.close();
			}
		} catch (SQLException e) {
			System.err.println("Unabled to close connection!!! " + e.getMessage());
		}
		conns.set(null);
	}

	
}
